diff --git a/uefi/linaro-edk2/OptionRomPkg/UndiRuntimeDxe/Init.c b/uefi/linaro-edk2/OptionRomPkg/UndiRuntimeDxe/Init.c
new file mode 100644
index 0000000..9410fe1
--- /dev/null
+++ b/uefi/linaro-edk2/OptionRomPkg/UndiRuntimeDxe/Init.c
@@ -0,0 +1,1049 @@
+/** @file
+  Initialization functions for EFI UNDI32 driver.
+
+Copyright (c) 2006 - 2013, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include "Undi32.h"
+//
+// Global Variables
+//
+
+PXE_SW_UNDI             *pxe_31 = NULL;  // 3.1 entry
+UNDI32_DEV              *UNDI32DeviceList[MAX_NIC_INTERFACES];
+UNDI_CONFIG_TABLE       *UndiDataPointer = NULL;
+
+//
+// UNDI Class Driver Global Variables
+//
+EFI_DRIVER_BINDING_PROTOCOL  gUndiDriverBinding = {
+  UndiDriverSupported,
+  UndiDriverStart,
+  UndiDriverStop,
+  0xa,
+  NULL,
+  NULL
+};
+
+
+/**
+  When address mapping changes to virtual this should make the appropriate
+  address conversions.
+
+  (Standard Event handler)
+
+  @return None
+
+**/
+VOID
+EFIAPI
+UndiNotifyVirtual (
+  EFI_EVENT Event,
+  VOID      *Context
+  )
+{
+  UINT16  Index;
+  VOID    *Pxe31Pointer;
+
+  if (pxe_31 != NULL) {
+    Pxe31Pointer = (VOID *) pxe_31;
+
+    EfiConvertPointer (
+      EFI_OPTIONAL_PTR,
+      (VOID **) &Pxe31Pointer
+      );
+
+    //
+    // UNDI32DeviceList is an array of pointers
+    //
+    for (Index = 0; Index < (pxe_31->IFcnt | pxe_31->IFcntExt << 8); Index++) {
+      UNDI32DeviceList[Index]->NIIProtocol_31.Id = (UINT64) (UINTN) Pxe31Pointer;
+      EfiConvertPointer (
+        EFI_OPTIONAL_PTR,
+        (VOID **) &(UNDI32DeviceList[Index])
+        );
+    }
+
+    EfiConvertPointer (
+      EFI_OPTIONAL_PTR,
+      (VOID **) &(pxe_31->EntryPoint)
+      );
+    pxe_31 = Pxe31Pointer;
+  }
+
+  for (Index = 0; Index <= PXE_OPCODE_LAST_VALID; Index++) {
+    EfiConvertPointer (
+      EFI_OPTIONAL_PTR,
+      (VOID **) &api_table[Index].api_ptr
+      );
+  }
+}
+
+
+/**
+  When EFI is shuting down the boot services, we need to install a
+  configuration table for UNDI to work at runtime!
+
+  (Standard Event handler)
+
+  @return None
+
+**/
+VOID
+EFIAPI
+UndiNotifyExitBs (
+  EFI_EVENT Event,
+  VOID      *Context
+  )
+{
+  InstallConfigTable ();
+}
+
+
+/**
+  Test to see if this driver supports ControllerHandle. Any ControllerHandle
+  than contains a  DevicePath, PciIo protocol, Class code of 2, Vendor ID of 0x8086,
+  and DeviceId of (D100_DEVICE_ID || D102_DEVICE_ID || ICH3_DEVICE_ID_1 ||
+  ICH3_DEVICE_ID_2 || ICH3_DEVICE_ID_3 || ICH3_DEVICE_ID_4 || ICH3_DEVICE_ID_5 ||
+  ICH3_DEVICE_ID_6 || ICH3_DEVICE_ID_7 || ICH3_DEVICE_ID_8) can be supported.
+
+  @param  This                 Protocol instance pointer.
+  @param  Controller           Handle of device to test.
+  @param  RemainingDevicePath  Not used.
+
+  @retval EFI_SUCCESS          This driver supports this device.
+  @retval other                This driver does not support this device.
+
+**/
+EFI_STATUS
+EFIAPI
+UndiDriverSupported (
+  IN EFI_DRIVER_BINDING_PROTOCOL    *This,
+  IN EFI_HANDLE                     Controller,
+  IN EFI_DEVICE_PATH_PROTOCOL       *RemainingDevicePath
+  )
+{
+  EFI_STATUS          Status;
+  EFI_PCI_IO_PROTOCOL *PciIo;
+  PCI_TYPE00          Pci;
+
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiDevicePathProtocolGuid,
+                  NULL,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_TEST_PROTOCOL
+                  );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiPciIoProtocolGuid,
+                  (VOID **) &PciIo,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = PciIo->Pci.Read (
+                        PciIo,
+                        EfiPciIoWidthUint8,
+                        0,
+                        sizeof (PCI_CONFIG_HEADER),
+                        &Pci
+                        );
+
+  if (!EFI_ERROR (Status)) {
+    Status = EFI_UNSUPPORTED;
+
+    if (Pci.Hdr.ClassCode[2] == 0x02 && Pci.Hdr.VendorId == PCI_VENDOR_ID_INTEL) {
+      switch (Pci.Hdr.DeviceId) {
+      case D100_DEVICE_ID:
+      case D102_DEVICE_ID:
+      case ICH3_DEVICE_ID_1:
+      case ICH3_DEVICE_ID_2:
+      case ICH3_DEVICE_ID_3:
+      case ICH3_DEVICE_ID_4:
+      case ICH3_DEVICE_ID_5:
+      case ICH3_DEVICE_ID_6:
+      case ICH3_DEVICE_ID_7:
+      case ICH3_DEVICE_ID_8:
+      case 0x1039:
+      case 0x103A:
+      case 0x103B:
+      case 0x103C:
+      case 0x103D:
+      case 0x103E:
+      case 0x1050:
+      case 0x1051:
+      case 0x1052:
+      case 0x1053:
+      case 0x1054:
+      case 0x1055:
+      case 0x1056:
+      case 0x1057:
+      case 0x1059:
+      case 0x1064:
+        Status = EFI_SUCCESS;
+      }
+    }
+  }
+
+  gBS->CloseProtocol (
+        Controller,
+        &gEfiPciIoProtocolGuid,
+        This->DriverBindingHandle,
+        Controller
+        );
+
+  return Status;
+}
+
+
+/**
+  Start this driver on Controller by opening PciIo and DevicePath protocol.
+  Initialize PXE structures, create a copy of the Controller Device Path with the
+  NIC's MAC address appended to it, install the NetworkInterfaceIdentifier protocol
+  on the newly created Device Path.
+
+  @param  This                 Protocol instance pointer.
+  @param  Controller           Handle of device to work with.
+  @param  RemainingDevicePath  Not used, always produce all possible children.
+
+  @retval EFI_SUCCESS          This driver is added to Controller.
+  @retval other                This driver does not support this device.
+
+**/
+EFI_STATUS
+EFIAPI
+UndiDriverStart (
+  IN EFI_DRIVER_BINDING_PROTOCOL    *This,
+  IN EFI_HANDLE                     Controller,
+  IN EFI_DEVICE_PATH_PROTOCOL       *RemainingDevicePath
+  )
+{
+  EFI_STATUS                Status;
+  EFI_DEVICE_PATH_PROTOCOL  *UndiDevicePath;
+  PCI_CONFIG_HEADER         *CfgHdr;
+  UNDI32_DEV                *UNDI32Device;
+  UINT16                    NewCommand;
+  UINT8                     *TmpPxePointer;
+  EFI_PCI_IO_PROTOCOL       *PciIoFncs;
+  UINTN                     Len;
+  UINT64                    Supports;
+  BOOLEAN                   PciAttributesSaved;
+
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiPciIoProtocolGuid,
+                  (VOID **) &PciIoFncs,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiDevicePathProtocolGuid,
+                  (VOID **) &UndiDevicePath,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+
+  if (EFI_ERROR (Status)) {
+    gBS->CloseProtocol (
+          Controller,
+          &gEfiPciIoProtocolGuid,
+          This->DriverBindingHandle,
+          Controller
+          );
+
+    return Status;
+  }
+
+  PciAttributesSaved = FALSE;
+
+  Status = gBS->AllocatePool (
+                  EfiRuntimeServicesData,
+                  sizeof (UNDI32_DEV),
+                  (VOID **) &UNDI32Device
+                  );
+
+  if (EFI_ERROR (Status)) {
+    goto UndiError;
+  }
+
+  ZeroMem ((CHAR8 *) UNDI32Device, sizeof (UNDI32_DEV));
+
+  //
+  // Get original PCI attributes
+  //
+  Status = PciIoFncs->Attributes (
+                    PciIoFncs,
+                    EfiPciIoAttributeOperationGet,
+                    0,
+                    &UNDI32Device->NicInfo.OriginalPciAttributes
+                    );
+
+  if (EFI_ERROR (Status)) {
+    goto UndiErrorDeleteDevice;
+  }
+  PciAttributesSaved = TRUE;
+
+  //
+  // allocate and initialize both (old and new) the !pxe structures here,
+  // there should only be one copy of each of these structure for any number
+  // of NICs this undi supports. Also, these structures need to be on a
+  // paragraph boundary as per the spec. so, while allocating space for these,
+  // make sure that there is space for 2 !pxe structures (old and new) and a
+  // 32 bytes padding for alignment adjustment (in case)
+  //
+  TmpPxePointer = NULL;
+  if (pxe_31 == NULL) {
+    Status = gBS->AllocatePool (
+                    EfiRuntimeServicesData,
+                    (sizeof (PXE_SW_UNDI) + sizeof (PXE_SW_UNDI) + 32),
+                    (VOID **) &TmpPxePointer
+                    );
+
+    if (EFI_ERROR (Status)) {
+      goto UndiErrorDeleteDevice;
+    }
+
+    ZeroMem (
+      TmpPxePointer,
+      sizeof (PXE_SW_UNDI) + sizeof (PXE_SW_UNDI) + 32
+      );
+    //
+    // check for paragraph alignment here, assuming that the pointer is
+    // already 8 byte aligned.
+    //
+    if (((UINTN) TmpPxePointer & 0x0F) != 0) {
+      pxe_31 = (PXE_SW_UNDI *) ((UINTN) (TmpPxePointer + 8));
+    } else {
+      pxe_31 = (PXE_SW_UNDI *) TmpPxePointer;
+    }
+
+    PxeStructInit (pxe_31);
+  }
+
+  UNDI32Device->NIIProtocol_31.Id = (UINT64) (UINTN) (pxe_31);
+
+  Status = PciIoFncs->Attributes (
+                        PciIoFncs,
+                        EfiPciIoAttributeOperationSupported,
+                        0,
+                        &Supports
+                        );
+  if (!EFI_ERROR (Status)) {
+    Supports &= EFI_PCI_DEVICE_ENABLE;
+    Status = PciIoFncs->Attributes (
+                          PciIoFncs,
+                          EfiPciIoAttributeOperationEnable,
+                          Supports,
+                          NULL
+                          );
+  }
+  //
+  // Read all the registers from device's PCI Configuration space
+  //
+  Status = PciIoFncs->Pci.Read (
+                            PciIoFncs,
+                            EfiPciIoWidthUint32,
+                            0,
+                            MAX_PCI_CONFIG_LEN,
+                            &UNDI32Device->NicInfo.Config
+                            );
+
+  CfgHdr = (PCI_CONFIG_HEADER *) &(UNDI32Device->NicInfo.Config[0]);
+
+  //
+  // make sure that this device is a PCI bus master
+  //
+
+  NewCommand = (UINT16) (CfgHdr->Command | PCI_COMMAND_MASTER | PCI_COMMAND_IO);
+  if (CfgHdr->Command != NewCommand) {
+    PciIoFncs->Pci.Write (
+                    PciIoFncs,
+                    EfiPciIoWidthUint16,
+                    PCI_COMMAND,
+                    1,
+                    &NewCommand
+                    );
+    CfgHdr->Command = NewCommand;
+  }
+
+  //
+  // make sure that the latency timer is at least 32
+  //
+  if (CfgHdr->LatencyTimer < 32) {
+    CfgHdr->LatencyTimer = 32;
+    PciIoFncs->Pci.Write (
+                    PciIoFncs,
+                    EfiPciIoWidthUint8,
+                    PCI_LATENCY_TIMER,
+                    1,
+                    &CfgHdr->LatencyTimer
+                    );
+  }
+  //
+  // the IfNum index for the current interface will be the total number
+  // of interfaces initialized so far
+  //
+  UNDI32Device->NIIProtocol_31.IfNum  = pxe_31->IFcnt | pxe_31->IFcntExt << 8;
+
+  PxeUpdate (&UNDI32Device->NicInfo, pxe_31);
+
+  UNDI32Device->NicInfo.Io_Function                    = PciIoFncs;
+  UNDI32DeviceList[UNDI32Device->NIIProtocol_31.IfNum] = UNDI32Device;
+  UNDI32Device->Undi32BaseDevPath                      = UndiDevicePath;
+
+  Status = AppendMac2DevPath (
+            &UNDI32Device->Undi32DevPath,
+            UNDI32Device->Undi32BaseDevPath,
+            &UNDI32Device->NicInfo
+            );
+
+  if (Status != 0) {
+    goto UndiErrorDeletePxe;
+  }
+
+  UNDI32Device->Signature                     = UNDI_DEV_SIGNATURE;
+
+  UNDI32Device->NIIProtocol_31.Revision       = EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL_REVISION_31;
+  UNDI32Device->NIIProtocol_31.Type           = EfiNetworkInterfaceUndi;
+  UNDI32Device->NIIProtocol_31.MajorVer       = PXE_ROMID_MAJORVER;
+  UNDI32Device->NIIProtocol_31.MinorVer       = PXE_ROMID_MINORVER_31;
+  UNDI32Device->NIIProtocol_31.ImageSize      = 0;
+  UNDI32Device->NIIProtocol_31.ImageAddr      = 0;
+  UNDI32Device->NIIProtocol_31.Ipv6Supported  = FALSE;
+
+  UNDI32Device->NIIProtocol_31.StringId[0]    = 'U';
+  UNDI32Device->NIIProtocol_31.StringId[1]    = 'N';
+  UNDI32Device->NIIProtocol_31.StringId[2]    = 'D';
+  UNDI32Device->NIIProtocol_31.StringId[3]    = 'I';
+
+  UNDI32Device->DeviceHandle                  = NULL;
+
+  //
+  // install both the 3.0 and 3.1 NII protocols.
+  //
+  Status = gBS->InstallMultipleProtocolInterfaces (
+                  &UNDI32Device->DeviceHandle,
+                  &gEfiNetworkInterfaceIdentifierProtocolGuid_31,
+                  &UNDI32Device->NIIProtocol_31,
+                  &gEfiDevicePathProtocolGuid,
+                  UNDI32Device->Undi32DevPath,
+                  NULL
+                  );
+
+  if (EFI_ERROR (Status)) {
+    goto UndiErrorDeleteDevicePath;
+  }
+
+  //
+  // if the table exists, free it and alloc again, or alloc it directly
+  //
+  if (UndiDataPointer != NULL) {
+    Status = gBS->FreePool(UndiDataPointer);
+  }
+  if (EFI_ERROR (Status)) {
+    goto UndiErrorDeleteDevicePath;
+  }
+
+  Len = ((pxe_31->IFcnt|pxe_31->IFcntExt << 8)* sizeof (UndiDataPointer->NII_entry)) + sizeof (UndiDataPointer);
+  Status = gBS->AllocatePool (EfiRuntimeServicesData, Len, (VOID **) &UndiDataPointer);
+
+  if (EFI_ERROR (Status)) {
+    goto UndiErrorAllocDataPointer;
+  }
+
+  //
+  // Open For Child Device
+  //
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiPciIoProtocolGuid,
+                  (VOID **) &PciIoFncs,
+                  This->DriverBindingHandle,
+                  UNDI32Device->DeviceHandle,
+                  EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER
+                  );
+
+  return EFI_SUCCESS;
+UndiErrorAllocDataPointer:
+  gBS->UninstallMultipleProtocolInterfaces (
+                  &UNDI32Device->DeviceHandle,
+                  &gEfiNetworkInterfaceIdentifierProtocolGuid_31,
+                  &UNDI32Device->NIIProtocol_31,
+                  &gEfiDevicePathProtocolGuid,
+                  UNDI32Device->Undi32DevPath,
+                  NULL
+                  );
+
+UndiErrorDeleteDevicePath:
+  UNDI32DeviceList[UNDI32Device->NIIProtocol_31.IfNum] = NULL;
+  gBS->FreePool (UNDI32Device->Undi32DevPath);
+
+UndiErrorDeletePxe:
+  PxeUpdate (NULL, pxe_31);
+  if (TmpPxePointer != NULL) {
+    gBS->FreePool (TmpPxePointer);
+
+  }
+
+UndiErrorDeleteDevice:
+  if (PciAttributesSaved) {
+    //
+    // Restore original PCI attributes
+    //
+    PciIoFncs->Attributes (
+                    PciIoFncs,
+                    EfiPciIoAttributeOperationSet,
+                    UNDI32Device->NicInfo.OriginalPciAttributes,
+                    NULL
+                    );
+  }
+
+  gBS->FreePool (UNDI32Device);
+
+UndiError:
+  gBS->CloseProtocol (
+        Controller,
+        &gEfiDevicePathProtocolGuid,
+        This->DriverBindingHandle,
+        Controller
+        );
+
+  gBS->CloseProtocol (
+        Controller,
+        &gEfiPciIoProtocolGuid,
+        This->DriverBindingHandle,
+        Controller
+        );
+
+  return Status;
+}
+
+
+/**
+  Stop this driver on Controller by removing NetworkInterfaceIdentifier protocol and
+  closing the DevicePath and PciIo protocols on Controller.
+
+  @param  This                 Protocol instance pointer.
+  @param  Controller           Handle of device to stop driver on.
+  @param  NumberOfChildren     How many children need to be stopped.
+  @param  ChildHandleBuffer    Not used.
+
+  @retval EFI_SUCCESS          This driver is removed Controller.
+  @retval other                This driver was not removed from this device.
+
+**/
+// TODO:    EFI_DEVICE_ERROR - add return value to function comment
+EFI_STATUS
+EFIAPI
+UndiDriverStop (
+  IN  EFI_DRIVER_BINDING_PROTOCOL    *This,
+  IN  EFI_HANDLE                     Controller,
+  IN  UINTN                          NumberOfChildren,
+  IN  EFI_HANDLE                     *ChildHandleBuffer
+  )
+{
+  EFI_STATUS                                Status;
+  BOOLEAN                                   AllChildrenStopped;
+  UINTN                                     Index;
+  UNDI32_DEV                                *UNDI32Device;
+  EFI_NETWORK_INTERFACE_IDENTIFIER_PROTOCOL *NIIProtocol;
+
+  //
+  // Complete all outstanding transactions to Controller.
+  // Don't allow any new transaction to Controller to be started.
+  //
+  if (NumberOfChildren == 0) {
+
+    //
+    // Close the bus driver
+    //
+    Status = gBS->CloseProtocol (
+                    Controller,
+                    &gEfiDevicePathProtocolGuid,
+                    This->DriverBindingHandle,
+                    Controller
+                    );
+
+    Status = gBS->CloseProtocol (
+                    Controller,
+                    &gEfiPciIoProtocolGuid,
+                    This->DriverBindingHandle,
+                    Controller
+                    );
+
+    return Status;
+  }
+
+  AllChildrenStopped = TRUE;
+
+  for (Index = 0; Index < NumberOfChildren; Index++) {
+
+    Status = gBS->OpenProtocol (
+                    ChildHandleBuffer[Index],
+                    &gEfiNetworkInterfaceIdentifierProtocolGuid_31,
+                    (VOID **) &NIIProtocol,
+                    This->DriverBindingHandle,
+                    Controller,
+                    EFI_OPEN_PROTOCOL_GET_PROTOCOL
+                    );
+    if (!EFI_ERROR (Status)) {
+
+      UNDI32Device = UNDI_DEV_FROM_THIS (NIIProtocol);
+
+      Status = gBS->CloseProtocol (
+                      Controller,
+                      &gEfiPciIoProtocolGuid,
+                      This->DriverBindingHandle,
+                      ChildHandleBuffer[Index]
+                      );
+      if (!EFI_ERROR (Status)) {
+        Status = gBS->UninstallMultipleProtocolInterfaces (
+                        ChildHandleBuffer[Index],
+                        &gEfiDevicePathProtocolGuid,
+                        UNDI32Device->Undi32DevPath,
+                        &gEfiNetworkInterfaceIdentifierProtocolGuid_31,
+                        &UNDI32Device->NIIProtocol_31,
+                        NULL
+                        );
+        if (!EFI_ERROR (Status)) {
+          //
+          // Restore original PCI attributes
+          //
+          Status = UNDI32Device->NicInfo.Io_Function->Attributes (
+                                                        UNDI32Device->NicInfo.Io_Function,
+                                                        EfiPciIoAttributeOperationSet,
+                                                        UNDI32Device->NicInfo.OriginalPciAttributes,
+                                                        NULL
+                                                        );
+
+          ASSERT_EFI_ERROR (Status);
+
+          gBS->FreePool (UNDI32Device->Undi32DevPath);
+          gBS->FreePool (UNDI32Device);
+
+        }
+      }
+    }
+
+    if (EFI_ERROR (Status)) {
+      AllChildrenStopped = FALSE;
+    }
+  }
+
+  if (!AllChildrenStopped) {
+    return EFI_DEVICE_ERROR;
+  }
+
+  return EFI_SUCCESS;
+
+}
+
+
+/**
+  Use the EFI boot services to produce a pause. This is also the routine which
+  gets replaced during RunTime by the O/S in the NIC_DATA_INSTANCE so it can
+  do it's own pause.
+
+  @param  UnqId                Runtime O/S routine might use this, this temp
+                               routine does not use it
+  @param  MicroSeconds         Determines the length of pause.
+
+  @return none
+
+**/
+VOID
+TmpDelay (
+  IN UINT64 UnqId,
+  IN UINTN  MicroSeconds
+  )
+{
+  gBS->Stall ((UINT32) MicroSeconds);
+}
+
+
+/**
+  Use the PCI IO abstraction to issue memory or I/O reads and writes.  This is also the routine which
+  gets replaced during RunTime by the O/S in the NIC_DATA_INSTANCE so it can do it's own I/O abstractions.
+
+  @param  UnqId                Runtime O/S routine may use this field, this temp
+                               routine does not.
+  @param  ReadWrite            Determine if it is an I/O or Memory Read/Write
+                               Operation.
+  @param  Len                  Determines the width of the data operation.
+  @param  Port                 What port to Read/Write from.
+  @param  BuffAddr             Address to read to or write from.
+
+  @return none
+
+**/
+VOID
+TmpMemIo (
+  IN UINT64 UnqId,
+  IN UINT8  ReadWrite,
+  IN UINT8  Len,
+  IN UINT64 Port,
+  IN UINT64 BuffAddr
+  )
+{
+  EFI_PCI_IO_PROTOCOL_WIDTH Width;
+  NIC_DATA_INSTANCE         *AdapterInfo;
+
+  Width       = (EFI_PCI_IO_PROTOCOL_WIDTH) 0;
+  AdapterInfo = (NIC_DATA_INSTANCE *) (UINTN) UnqId;
+  switch (Len) {
+  case 2:
+    Width = (EFI_PCI_IO_PROTOCOL_WIDTH) 1;
+    break;
+
+  case 4:
+    Width = (EFI_PCI_IO_PROTOCOL_WIDTH) 2;
+    break;
+
+  case 8:
+    Width = (EFI_PCI_IO_PROTOCOL_WIDTH) 3;
+    break;
+  }
+
+  switch (ReadWrite) {
+  case PXE_IO_READ:
+    AdapterInfo->Io_Function->Io.Read (
+                                  AdapterInfo->Io_Function,
+                                  Width,
+                                  1,
+                                  Port,
+                                  1,
+                                  (VOID *) (UINTN) (BuffAddr)
+                                  );
+    break;
+
+  case PXE_IO_WRITE:
+    AdapterInfo->Io_Function->Io.Write (
+                                  AdapterInfo->Io_Function,
+                                  Width,
+                                  1,
+                                  Port,
+                                  1,
+                                  (VOID *) (UINTN) (BuffAddr)
+                                  );
+    break;
+
+  case PXE_MEM_READ:
+    AdapterInfo->Io_Function->Mem.Read (
+                                    AdapterInfo->Io_Function,
+                                    Width,
+                                    0,
+                                    Port,
+                                    1,
+                                    (VOID *) (UINTN) (BuffAddr)
+                                    );
+    break;
+
+  case PXE_MEM_WRITE:
+    AdapterInfo->Io_Function->Mem.Write (
+                                    AdapterInfo->Io_Function,
+                                    Width,
+                                    0,
+                                    Port,
+                                    1,
+                                    (VOID *) (UINTN) (BuffAddr)
+                                    );
+    break;
+  }
+
+  return ;
+}
+
+
+/**
+  Using the NIC data structure information, read the EEPROM to get the MAC address and then allocate space
+  for a new devicepath (**DevPtr) which will contain the original device path the NIC was found on (*BaseDevPtr)
+  and an added MAC node.
+
+  @param  DevPtr               Pointer which will point to the newly created device
+                               path with the MAC node attached.
+  @param  BaseDevPtr           Pointer to the device path which the UNDI device
+                               driver is latching on to.
+  @param  AdapterInfo          Pointer to the NIC data structure information which
+                               the UNDI driver is layering on..
+
+  @retval EFI_SUCCESS          A MAC address was successfully appended to the Base
+                               Device Path.
+  @retval other                Not enough resources available to create new Device
+                               Path node.
+
+**/
+EFI_STATUS
+AppendMac2DevPath (
+  IN OUT  EFI_DEVICE_PATH_PROTOCOL **DevPtr,
+  IN      EFI_DEVICE_PATH_PROTOCOL *BaseDevPtr,
+  IN      NIC_DATA_INSTANCE        *AdapterInfo
+  )
+{
+  EFI_MAC_ADDRESS           MACAddress;
+  PCI_CONFIG_HEADER         *CfgHdr;
+  INT32                     Val;
+  INT32                     Index;
+  INT32                     Index2;
+  UINT8                     AddrLen;
+  MAC_ADDR_DEVICE_PATH      MacAddrNode;
+  EFI_DEVICE_PATH_PROTOCOL  *EndNode;
+  UINT8                     *DevicePtr;
+  UINT16                    TotalPathLen;
+  UINT16                    BasePathLen;
+  EFI_STATUS                Status;
+
+  //
+  // set the environment ready (similar to UNDI_Start call) so that we can
+  // execute the other UNDI_ calls to get the mac address
+  // we are using undi 3.1 style
+  //
+  AdapterInfo->Delay      = TmpDelay;
+  AdapterInfo->Virt2Phys  = (VOID *) 0;
+  AdapterInfo->Block      = (VOID *) 0;
+  AdapterInfo->Map_Mem    = (VOID *) 0;
+  AdapterInfo->UnMap_Mem  = (VOID *) 0;
+  AdapterInfo->Sync_Mem   = (VOID *) 0;
+  AdapterInfo->Mem_Io     = TmpMemIo;
+  //
+  // these tmp call-backs follow 3.1 undi style
+  // i.e. they have the unique_id parameter.
+  //
+  AdapterInfo->VersionFlag  = 0x31;
+  AdapterInfo->Unique_ID    = (UINT64) (UINTN) AdapterInfo;
+
+  //
+  // undi init portion
+  //
+  CfgHdr              = (PCI_CONFIG_HEADER *) &(AdapterInfo->Config[0]);
+  AdapterInfo->ioaddr = 0;
+  AdapterInfo->RevID  = CfgHdr->RevID;
+
+  AddrLen             = E100bGetEepromAddrLen (AdapterInfo);
+
+  for (Index = 0, Index2 = 0; Index < 3; Index++) {
+    Val                       = E100bReadEeprom (AdapterInfo, Index, AddrLen);
+    MACAddress.Addr[Index2++] = (UINT8) Val;
+    MACAddress.Addr[Index2++] = (UINT8) (Val >> 8);
+  }
+
+  SetMem (MACAddress.Addr + Index2, sizeof (EFI_MAC_ADDRESS) - Index2, 0);
+  //for (; Index2 < sizeof (EFI_MAC_ADDRESS); Index2++) {
+  //  MACAddress.Addr[Index2] = 0;
+  //}
+  //
+  // stop undi
+  //
+  AdapterInfo->Delay  = (VOID *) 0;
+  AdapterInfo->Mem_Io = (VOID *) 0;
+
+  //
+  // fill the mac address node first
+  //
+  ZeroMem ((CHAR8 *) &MacAddrNode, sizeof MacAddrNode);
+  CopyMem (
+    (CHAR8 *) &MacAddrNode.MacAddress,
+    (CHAR8 *) &MACAddress,
+    sizeof (EFI_MAC_ADDRESS)
+    );
+
+  MacAddrNode.Header.Type       = MESSAGING_DEVICE_PATH;
+  MacAddrNode.Header.SubType    = MSG_MAC_ADDR_DP;
+  MacAddrNode.Header.Length[0]  = (UINT8) sizeof (MacAddrNode);
+  MacAddrNode.Header.Length[1]  = 0;
+
+  //
+  // find the size of the base dev path.
+  //
+  EndNode = BaseDevPtr;
+
+  while (!IsDevicePathEnd (EndNode)) {
+    EndNode = NextDevicePathNode (EndNode);
+  }
+
+  BasePathLen = (UINT16) ((UINTN) (EndNode) - (UINTN) (BaseDevPtr));
+
+  //
+  // create space for full dev path
+  //
+  TotalPathLen = (UINT16) (BasePathLen + sizeof (MacAddrNode) + sizeof (EFI_DEVICE_PATH_PROTOCOL));
+
+  Status = gBS->AllocatePool (
+                  EfiRuntimeServicesData,
+                  TotalPathLen,
+                  (VOID **) &DevicePtr
+                  );
+
+  if (Status != EFI_SUCCESS) {
+    return Status;
+  }
+  //
+  // copy the base path, mac addr and end_dev_path nodes
+  //
+  *DevPtr = (EFI_DEVICE_PATH_PROTOCOL *) DevicePtr;
+  CopyMem (DevicePtr, (CHAR8 *) BaseDevPtr, BasePathLen);
+  DevicePtr += BasePathLen;
+  CopyMem (DevicePtr, (CHAR8 *) &MacAddrNode, sizeof (MacAddrNode));
+  DevicePtr += sizeof (MacAddrNode);
+  CopyMem (DevicePtr, (CHAR8 *) EndNode, sizeof (EFI_DEVICE_PATH_PROTOCOL));
+
+  return EFI_SUCCESS;
+}
+
+
+/**
+  Install a GUID/Pointer pair into the system's configuration table.
+
+  none
+
+  @retval EFI_SUCCESS          Install a GUID/Pointer pair into the system's
+                               configuration table.
+  @retval other                Did not successfully install the GUID/Pointer pair
+                               into the configuration table.
+
+**/
+// TODO:    VOID - add argument and description to function comment
+EFI_STATUS
+InstallConfigTable (
+  IN VOID
+  )
+{
+  EFI_STATUS              Status;
+  EFI_CONFIGURATION_TABLE *CfgPtr;
+  UNDI_CONFIG_TABLE       *TmpData;
+  UINT16                  Index;
+  UNDI_CONFIG_TABLE       *UndiData;
+
+  if (pxe_31 == NULL) {
+    return EFI_SUCCESS;
+  }
+
+  if(UndiDataPointer == NULL) {
+    return EFI_SUCCESS;
+  }
+
+  UndiData = (UNDI_CONFIG_TABLE *)UndiDataPointer;
+
+  UndiData->NumberOfInterfaces  = (pxe_31->IFcnt | pxe_31->IFcntExt << 8);
+  UndiData->nextlink            = NULL;
+
+  for (Index = 0; Index < (pxe_31->IFcnt | pxe_31->IFcntExt << 8); Index++) {
+    UndiData->NII_entry[Index].NII_InterfacePointer = &UNDI32DeviceList[Index]->NIIProtocol_31;
+    UndiData->NII_entry[Index].DevicePathPointer    = UNDI32DeviceList[Index]->Undi32DevPath;
+  }
+
+  //
+  // see if there is an entry in the config table already
+  //
+  CfgPtr = gST->ConfigurationTable;
+
+  for (Index = 0; Index < gST->NumberOfTableEntries; Index++) {
+    Status = CompareGuid (
+              &CfgPtr->VendorGuid,
+              &gEfiNetworkInterfaceIdentifierProtocolGuid_31
+              );
+    if (Status != EFI_SUCCESS) {
+      break;
+    }
+
+    CfgPtr++;
+  }
+
+  if (Index < gST->NumberOfTableEntries) {
+    TmpData = (UNDI_CONFIG_TABLE *) CfgPtr->VendorTable;
+
+    //
+    // go to the last link
+    //
+    while (TmpData->nextlink != NULL) {
+      TmpData = TmpData->nextlink;
+    }
+
+    TmpData->nextlink = UndiData;
+
+    //
+    // 1st one in chain
+    //
+    UndiData = (UNDI_CONFIG_TABLE *) CfgPtr->VendorTable;
+  }
+
+  //
+  // create an entry in the configuration table for our GUID
+  //
+  Status = gBS->InstallConfigurationTable (
+                  &gEfiNetworkInterfaceIdentifierProtocolGuid_31,
+                  UndiData
+                  );
+  return Status;
+}
+
+/**
+
+**/
+EFI_STATUS
+EFIAPI
+InitializeUndi(
+  IN EFI_HANDLE           ImageHandle,
+  IN EFI_SYSTEM_TABLE     *SystemTable
+  )
+{
+  EFI_EVENT     Event;
+  EFI_STATUS    Status;
+
+  Status = EfiLibInstallDriverBindingComponentName2 (
+             ImageHandle,
+             SystemTable,
+             &gUndiDriverBinding,
+             ImageHandle,
+             &gUndiComponentName,
+             &gUndiComponentName2
+             );
+  ASSERT_EFI_ERROR (Status);
+
+  Status = gBS->CreateEventEx (
+                  EVT_NOTIFY_SIGNAL,
+                  TPL_NOTIFY,
+                  UndiNotifyExitBs,
+                  NULL,
+                  &gEfiEventExitBootServicesGuid,
+                  &Event
+                  );
+  ASSERT_EFI_ERROR (Status);
+
+  Status = gBS->CreateEventEx (
+                  EVT_NOTIFY_SIGNAL,
+                  TPL_NOTIFY,
+                  UndiNotifyVirtual,
+                  NULL,
+                  &gEfiEventVirtualAddressChangeGuid,
+                  &Event
+                  );
+  ASSERT_EFI_ERROR (Status);
+
+  return Status;
+}
